package com.gzhryc.shared_device.oem.h5.agent.controllers.api.v1.place;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.servlet.http.HttpServletRequest;

import com.gzhryc.common.StringTools;
import com.gzhryc.common.api.DefaultAPIResponse;
import com.gzhryc.common.data.TreeUtils;
import com.gzhryc.common.exceptions.LogicException;
import com.gzhryc.common.logging.Logger;
import com.gzhryc.servlet.WebUtils;
import com.gzhryc.servlet.annotation.Route;
import com.gzhryc.shared_device.base.enums.ENetworkType;
import com.gzhryc.shared_device.bxscn.code.dao.db.PortableEnergyBatteryType;
import com.gzhryc.shared_device.bxscn.code.dao.models.PortableEnergyBatteryTypeCount;
import com.gzhryc.shared_device.bxscn.code.services.PortableEnergyBatteryService;
import com.gzhryc.shared_device.bxscn.code.services.PortableEnergyBatteryTypeService;
import com.gzhryc.shared_device.common.device.dao.db.Device;
import com.gzhryc.shared_device.common.device.dao.db.DeviceType;
import com.gzhryc.shared_device.common.device.dao.db.DeviceTypeFunc;
import com.gzhryc.shared_device.common.device.dao.models.DeviceTypeCount;
import com.gzhryc.shared_device.common.device.services.DeviceService;
import com.gzhryc.shared_device.common.device.services.DeviceTypeFuncService;
import com.gzhryc.shared_device.common.device.services.DeviceTypeService;
import com.gzhryc.shared_device.oem.code.BaseConstants;
import com.gzhryc.shared_device.oem.code.device.EDeviceFunCode;
import com.gzhryc.shared_device.oem.code.place.dao.db.PlaceBusinessConfig;
import com.gzhryc.shared_device.oem.code.place.dao.db.PlacePhysicalStore;
import com.gzhryc.shared_device.oem.code.place.dao.db.PlacePhysicalStoreType;
import com.gzhryc.shared_device.oem.code.place.services.PlaceBusinessConfigService;
import com.gzhryc.shared_device.oem.code.place.services.PlacePhysicalStoreService;
import com.gzhryc.shared_device.oem.code.place.services.PlacePhysicalStoreTypeService;
import com.gzhryc.shared_device.oem.code.user.ERoleType;
import com.gzhryc.shared_device.oem.h5.agent.ClientAPICodeConstants;
import com.gzhryc.shared_device.oem.h5.agent.DeviceCostConfigUtils;
import com.gzhryc.shared_device.oem.h5.agent.LoginUser;
import com.gzhryc.shared_device.oem.h5.agent.WebConstants;
import com.gzhryc.shared_device.oem.h5.agent.dto.api.v1.place.PlaceBusinessConfigListRequest;
import com.gzhryc.shared_device.oem.h5.agent.dto.api.v1.place.PlaceBusinessConfigListResponse;
import com.gzhryc.shared_device.oem.h5.agent.dto.api.v1.place.PlaceBusinessTypeListRequest;
import com.gzhryc.shared_device.oem.h5.agent.dto.api.v1.place.PlaceBusinessTypeListResponse;
import com.gzhryc.shared_device.oem.h5.agent.dto.api.v1.place.PlaceCostChangeRequest;
import com.gzhryc.shared_device.oem.h5.agent.dto.api.v1.place.PlaceDeviceTypeListRequest;
import com.gzhryc.shared_device.oem.h5.agent.dto.api.v1.place.PlaceDeviceTypeListResponse;
import com.gzhryc.shared_device.oem.h5.agent.dto.api.v1.place.PlacePhysicalStoreTypeListResponse;

/**
 * 网点所有类型的公共接口，无权限检查
 * @version 2024-1-14
 */
public class PlaceTypeController {

    static Logger log = Logger.getLogger(PlaceTypeController.class);

    /**
     * 获取网点类型
     * @param request
     * @return
     */
    @Route(value = "/agent/api/v1/place/physical_store/type/select.data")
    public PlacePhysicalStoreTypeListResponse typeList(HttpServletRequest request){
        PlacePhysicalStoreTypeListResponse apiResp = new PlacePhysicalStoreTypeListResponse(ClientAPICodeConstants.NULL_DATA,"暂无数据");
        List<PlacePhysicalStoreType> data = PlacePhysicalStoreTypeService.self().findAll();
        if(data != null && data.size() > 0){
            List<PlacePhysicalStoreTypeListResponse.Item> items = TreeUtils.byTree(data, new TreeUtils.ConvertListen<PlacePhysicalStoreType,
                    PlacePhysicalStoreTypeListResponse.Item>() {
                @Override
                public PlacePhysicalStoreTypeListResponse.Item change(PlacePhysicalStoreType parent, PlacePhysicalStoreType obj) {
                    PlacePhysicalStoreTypeListResponse.Item item = new PlacePhysicalStoreTypeListResponse.Item();
                    item.setId(obj.getId());
                    item.setCode(obj.getCode());
                    item.setName(obj.getName());
                    item.setParentId(obj.getParentId());
                    return item;
                }
            });

            if(items != null && items.size() > 0){
                apiResp.setCode(ClientAPICodeConstants.SUCCESS,null);
                apiResp.getBody().setItems(items);
            }
        }
        return apiResp;
    }

    /**
     * 获取网点的业务类型
     * @param request
     * @return
     */
    @Route(value = "/agent/api/v1/place/business_type/list.data")
    public PlaceBusinessTypeListResponse findBusinessTypeList(HttpServletRequest request){
        PlaceBusinessTypeListResponse apiResp = new PlaceBusinessTypeListResponse(ClientAPICodeConstants.NULL_DATA, "暂无数据");
        PlaceBusinessTypeListRequest apiReq = WebUtils.getJsonRequest(request, PlaceBusinessTypeListRequest.class);
        if (apiReq != null && apiReq.getBody().getPlaceId() != null) {
            List<PlaceBusinessConfig> deviceFuncList = PlaceBusinessConfigService.self().findByPlaceId(apiReq.getBody().getPlaceId());
            if(deviceFuncList != null && deviceFuncList.size() > 0){
                apiResp.setCode(ClientAPICodeConstants.SUCCESS,null);
                apiResp.getBody().setItems(new ArrayList<>());
                for(PlaceBusinessConfig businessConfig : deviceFuncList){
                    PlaceBusinessTypeListResponse.Item item = new PlaceBusinessTypeListResponse.Item();
                    item.setBusinessType(businessConfig.getBusinessType());
                    item.setBusinessTypeName(businessConfig.getBusinessTypeName());
                    apiResp.getBody().getItems().add(item);
                }
            }
        }
        return apiResp;
    }

    @Route(value = "/agent/api/v1/place/business_type/save.do")
    public DefaultAPIResponse saveBusinessType(HttpServletRequest request) {
        DefaultAPIResponse apiResp = new DefaultAPIResponse(ClientAPICodeConstants.EXECUTE_ERROR, "切换失败，请稍后再试");
        PlaceCostChangeRequest apiReq = WebUtils.getJsonRequest(request, PlaceCostChangeRequest.class);
        if (apiReq != null && apiReq.getBody().getPlaceId() != null && StringTools.isNotBlank(apiReq.getBody().getBusinessType())) {
            LoginUser loginUser = WebUtils.getAttribute(request, WebConstants.ATTR_LOGIN_USER, LoginUser.class);
            if (loginUser != null && ERoleType.Agent.index().equals(loginUser.getRoleType())) {
                PlacePhysicalStore physicalStore = PlacePhysicalStoreService.self().getById(apiReq.getBody().getPlaceId());
                if(physicalStore == null){
                    apiResp.setMsg("未找到网点信息");
                    return apiResp;
                }
                if(!physicalStore.getUserId().equals(loginUser.getId())){
                    apiResp.setCode(ClientAPICodeConstants.NOT_POWER,"无权限操作");
                    return apiResp;
                }
                try {
                    PlaceBusinessConfig placeBusinessConfig = PlaceBusinessConfigService.self().getByKeys(apiReq.getBody().getPlaceId(), apiReq.getBody().getBusinessType());
                    if(placeBusinessConfig == null){
                        placeBusinessConfig = new PlaceBusinessConfig();
                        placeBusinessConfig.setPlaceId(apiReq.getBody().getPlaceId());
                        placeBusinessConfig.setBusinessType(apiReq.getBody().getBusinessType());
                        if(PlaceBusinessConfigService.self().add(placeBusinessConfig)){
                            apiResp.setCode(ClientAPICodeConstants.SUCCESS, null);
                        }
                    }else{
                        apiResp.setCode(ClientAPICodeConstants.SUCCESS, null);
                    }
                } catch (LogicException e) {
                    apiResp.setMsg(e.getMessage());
                }
            }
        }
        return apiResp;
    }

    @Route(value = "/agent/api/v1/place/business_config/list.data")
    public PlaceBusinessConfigListResponse businessConfigList(HttpServletRequest request) {
        PlaceBusinessConfigListResponse apiResp = new PlaceBusinessConfigListResponse(ClientAPICodeConstants.NULL_DATA, "暂无数据");
        PlaceBusinessConfigListRequest apiReq = WebUtils.getJsonRequest(request, PlaceBusinessConfigListRequest.class);
        if (apiReq != null && apiReq.getBody().getPlaceId() != null) {
            List<PlaceBusinessConfig> businessConfigList = PlaceBusinessConfigService.self().findByPlaceId(apiReq.getBody().getPlaceId());
            if(businessConfigList != null && businessConfigList.size() > 0){
                apiResp.setCode(ClientAPICodeConstants.SUCCESS,null);
                apiResp.getBody().setItems(new ArrayList<>());
                for(PlaceBusinessConfig businessConfig : businessConfigList){
                    PlaceBusinessConfigListResponse.Item item = DeviceCostConfigUtils.buildCostConfigItem(businessConfig);
                    if (item != null) {
                        apiResp.getBody().getItems().add(item);
                    }
                }
            }else {
            	//兼容代码，历史逻辑中没有在部署设备时添加业务类型
                List<Device> deviceList = DeviceService.self().findByPlaceId(apiReq.getBody().getPlaceId());
                if(deviceList != null && deviceList.size() > 0){
                    List<String> typeIds = new ArrayList<>();
                    Map<String,Integer> deviceCountMap = new HashMap<>();
                    for(Device device : deviceList){
                        if(!typeIds.contains(device.getDeviceTypeId())){
                            typeIds.add(device.getDeviceTypeId());
                        }
                        Integer deviceCount = deviceCountMap.get(device.getDeviceTypeId());
                        if(deviceCount == null){
                            deviceCount = 1;
                        }else{
                            deviceCount = deviceCount + 1;
                        }
                        deviceCountMap.put(device.getDeviceTypeId(),deviceCount);
                    }

                    List<DeviceTypeFunc> deviceTypeFuncList = DeviceTypeFuncService.self().findByTypeIds(typeIds);
                    if(deviceTypeFuncList != null && deviceTypeFuncList.size() > 0) {
                        Map<String,Integer> businessTypeMap = new HashMap<>();
                        for (DeviceTypeFunc deviceTypeFunc : deviceTypeFuncList) {
                            Integer deviceCount = businessTypeMap.get(deviceTypeFunc.getBusinessType());
                            if(deviceCount == null){
                                deviceCount = deviceCountMap.get(deviceTypeFunc.getTypeId());
                                businessTypeMap.put(deviceTypeFunc.getBusinessType(),deviceCount);
                            }
                        }

                        for (String businessType : businessTypeMap.keySet()) {
                            try {
                                Integer deviceCount = businessTypeMap.get(businessType);
                                PlaceBusinessConfig businessConfig = new PlaceBusinessConfig();
                                businessConfig.setPlaceId(apiReq.getBody().getPlaceId());
                                businessConfig.setBusinessType(businessType);
                                businessConfig.setDeviceCount(deviceCount);
                            }catch (Exception e){
                                log.error(e.getMessage(),e);
                            }
                        }
                    }
                }
            }
        }
        return apiResp;
    }

    @Route(value = "/agent/api/v1/place/device_type/list.data")
    public PlaceDeviceTypeListResponse deviceTypeList(HttpServletRequest request){
        PlaceDeviceTypeListResponse apiResp = new PlaceDeviceTypeListResponse(ClientAPICodeConstants.NULL_DATA,"暂无数据");
        PlaceDeviceTypeListRequest apiReq = WebUtils.getJsonRequest(request,PlaceDeviceTypeListRequest.class);
        if(apiReq != null && apiReq.getBody().getPlaceId() != null) {
            List<DeviceTypeCount> deviceTypeCountList = DeviceService.self().countDeviceTypeByPlaceId(apiReq.getBody().getPlaceId());
            if (deviceTypeCountList != null && deviceTypeCountList.size() > 0) {
                apiResp.setCode(ClientAPICodeConstants.SUCCESS, null);
                apiResp.getBody().setItems(new ArrayList<>());

                List<String> deviceTypeIds = new ArrayList<>();
                for (DeviceTypeCount deviceTypeCount : deviceTypeCountList) {
                    deviceTypeIds.add(deviceTypeCount.getDeviceTypeId());
                }

                List<DeviceType> deviceTypeList = DeviceTypeService.self().findByIds(deviceTypeIds);
                List<DeviceTypeFunc> deviceTypeFuncList = DeviceTypeFuncService.self().findByTypeIds(deviceTypeIds);

                String resDomain = WebConstants.getResDomain(request);

                if (deviceTypeFuncList != null && deviceTypeFuncList.size() > 0) {
                    for (DeviceType deviceType : deviceTypeList) {
                        for (DeviceTypeFunc deviceTypeFunc : deviceTypeFuncList) {
                            if (deviceTypeFunc.getTypeId().equals(deviceType.getId())) {
                                if (StringTools.isNotBlank(deviceType.getFuncCodeNames())) {
                                    deviceType.setFuncCodeNames(deviceType.getFuncCodeNames() + "," + EDeviceFunCode.note(deviceTypeFunc.getCode()));
                                } else {
                                    deviceType.setFuncCodeNames(EDeviceFunCode.note(deviceTypeFunc.getCode()));
                                }
                            }
                        }
                    }
                }

                for (DeviceTypeCount deviceTypeCount : deviceTypeCountList) {
                    PlaceDeviceTypeListResponse.Item item = new PlaceDeviceTypeListResponse.Item();
                    item.setDeviceTypeId(deviceTypeCount.getDeviceTypeId());
                    item.setDeviceCount(deviceTypeCount.getDeviceCount().intValue());

                    if (deviceTypeList != null && deviceTypeList.size() > 0) {
                        for (DeviceType deviceType : deviceTypeList) {
                            if (deviceType.getId().equals(deviceTypeCount.getDeviceTypeId())) {
                                item.setDeviceTypeName(deviceType.getName());
                                item.setDeviceTypeImg(WebUtils.setHttpDomain(resDomain, deviceType.getThumbnailImg()));
                                item.setNetworkType(deviceType.getNetworkType());
                                item.setNetworkTypeName(deviceType.getNetworkTypeName());
                                item.setFuncCodeNames(deviceType.getFuncCodeNames());
                                break;
                            }
                        }
                    }

                    apiResp.getBody().getItems().add(item);
                }
            }

            //检查是否支持储能电池
            if(BaseConstants.getBXSCN()) {
                //获取储能电池列表
                List<PortableEnergyBatteryTypeCount> batteryTypeCountList = PortableEnergyBatteryService.self().findTypeCountByPlaceId(apiReq.getBody().getPlaceId());
                if (batteryTypeCountList != null && batteryTypeCountList.size() > 0) {
                    if (apiResp.getBody().getItems() == null) {
                        apiResp.setCode(ClientAPICodeConstants.SUCCESS, null);
                        apiResp.getBody().setItems(new ArrayList<>());
                    }

                    List<String> batteryTypeIds = new ArrayList<>();
                    for (PortableEnergyBatteryTypeCount batteryTypeCount : batteryTypeCountList) {
                        batteryTypeIds.add(batteryTypeCount.getBatteryType());
                    }

                    List<PortableEnergyBatteryType> batteryTypeList = PortableEnergyBatteryTypeService.self().findByIds(batteryTypeIds);

                    for (PortableEnergyBatteryTypeCount batteryTypeCount : batteryTypeCountList) {
                        PlaceDeviceTypeListResponse.Item item = new PlaceDeviceTypeListResponse.Item();
                        item.setDeviceTypeId(batteryTypeCount.getBatteryType());
                        item.setDeviceCount(batteryTypeCount.getDeviceCount().intValue());

                        String resDomain = WebConstants.getResDomain(request);

                        if (batteryTypeList != null && batteryTypeList.size() > 0) {
                            for (PortableEnergyBatteryType batteryType : batteryTypeList) {
                                if (batteryType.getId().equals(batteryTypeCount.getBatteryType())) {
                                    item.setDeviceTypeName(batteryType.getName());
                                    item.setDeviceTypeImg(WebUtils.setHttpDomain(resDomain, batteryType.getThumbnailImg()));
                                    item.setNetworkType(ENetworkType.NotNetwork.index());
                                    item.setNetworkTypeName(ENetworkType.NotNetwork.note());
                                    item.setFuncCodeNames(EDeviceFunCode.BXSCN.note());
                                    break;
                                }
                            }
                        }
                        apiResp.getBody().getItems().add(item);
                    }
                }
            }
        }
        return apiResp;
    }
}
